package net.chasing.androidbaseconfig.util.thread;

import android.os.Handler;
import android.os.Looper;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

/**
 * 注意：使用该线程池，则执行的Runnable需要实现{@link Prioritized}或{@link Comparable}
 * 可以使用已经实现了Comparable的{@link ComparableRunnable}
 * <p>
 * 永久性任务直接创建线程执行，不需要使用线程池
 * 避免线程池核心线程占满，导致后面的线程无法执行
 */
public class ThreadPoolUtils {
    //参数初始化
    private static final int CPU_COUNT = Runtime.getRuntime().availableProcessors();
    //核心线程数量大小
    private static final int CORE_POOL_SIZE = Math.max(2, Math.min(CPU_COUNT + 1, 4));
    //线程池最大容纳线程数
    private static final int MAXIMUM_POOL_SIZE = CPU_COUNT * 2 + 1;

    private static final ThreadPoolUtils mThreadPoolUtils = new ThreadPoolUtils();
    //先进先出的线程池，具有优先级功能
    // CPU线程池：计算等，靠CPU处理的
    private final ThreadPoolExecutor mCPUThreadExecutor;
    //单个运行线程的线程池，控制顺序，一个线程执行完后才会继续下一个线程
    private final ExecutorService mSingeThreadExecutor;
    //主线程运行的Handler，处理在子线程回调之后需要在主线程刷新UI的操作哦
    private final Handler MAIN_THREAD_HANDLER;

    private ThreadPoolUtils() {
        mCPUThreadExecutor = new ThreadPoolExecutor(CORE_POOL_SIZE, MAXIMUM_POOL_SIZE);
        mSingeThreadExecutor = Executors.newSingleThreadExecutor();
        MAIN_THREAD_HANDLER = new Handler(Looper.getMainLooper()) {
        };
    }

    public static ThreadPoolUtils getInstance() {
        return mThreadPoolUtils;
    }

    public void execute(ComparableRunnable runnable) {
        mCPUThreadExecutor.execute(runnable);
    }

    //逐个执行Runnable，上个Runnable执行完后才会开始下个Runnable
    //单个线程操作类似bitmap时，内存开销太大，所以使用单个线程依次运行
    public void executeOneByOne(Runnable runnable) {
        mSingeThreadExecutor.execute(runnable);
    }

    public void executeOnMainThread(Runnable runnable) {
        MAIN_THREAD_HANDLER.post(runnable);
    }

    public void executeOnMainThread(Runnable runnable, int delay) {
        MAIN_THREAD_HANDLER.postDelayed(runnable, delay);
    }
}